import { ElNotification  } from 'element-plus'
import Setting from "@/public/config"

let URL = Setting.wsAddress
let timer = null
let ws = null
let isConnect = false
let checkHeart = 'check-heart'
let count = 0

// 心跳检测
let heart = {
	timer: null,
	timeout: 20000, // 每20s进行一次心跳检测
	start() {
		this.timer = setInterval(() => {
			if (isConnect) {
				ws.send(JSON.stringify(checkHeart))
			}
		}, this.timeout)
	},
	reset() {
		if(this.timer) clearTimeout(this.timer)
		this.start()
	},
	close() {
		clearTimeout(this.timer)
	}
}

// WebSocket连接
const connectWebsocket = () => {
	if (count > 5) {
		connectCount()
		return
	}
	try { // 正在建立连接
		ws = new WebSocket(URL)
		initWebSocket() // 初始化WebSocket连接
	} catch { // 建立连接出错，重新连接
		connect()
	}
}
// 重新连接WebSocket
function connect() {
	if (isConnect) return
	ElNotification({
		title: 'WebSocket',
		message: '尝试重新连接WebSocket',
		type: 'warning',
		position: 'bottom-right',
	})
	if (timer) clearTimeout(timer)
	timer = setTimeout(() => { // 每次连接 延迟5s
		count++
		connectWebsocket()
	}, 5000)
}
// 初始化WebSocket连接
function initWebSocket() {
	ws.onopen = function () { // WebSocket连接成功
		isConnect = true
		connectStatus(true)
		ElNotification({
			title: 'WebSocket',
			message: 'WebSocket连接成功',
			type: 'success',
			position: 'bottom-right',
		})
	}
	ws.onerror = function (e) { // WebSocket连接发生错误
		isConnect = false
		connectStatus(false)
		heart.start() // 开始心跳检测
		ElNotification({
			title: 'WebSocket',
			message: 'WebSocket连接发生错误,正在尝试重新连接',
			type: 'error',
			position: 'bottom-right',
		})
		setTimeout(() => {
			connect()
		}, 100);
	}
	ws.onclose = function (e) { // 已关闭WebSocket连接
		isConnect = false
		connectStatus(false)
		heart.close() // 关闭心跳检测
		ElNotification({
			title: 'WebSocket',
			message: '已关闭WebSocket连接,正在尝试重新连接',
			type: 'warning',
			position: 'bottom-right',
		})
	}
	ws.onmessage = function (e) { // 接收到服务端发送的数据
		heart.reset() // 重置心跳检测
		if (e.data === checkHeart) return // 心跳检测
		receive(e.data)
	}
}
function connectCount() {
	ElNotification({
		title: 'WebSocket',
		message: 'WebSocket连接失败',
		type: 'error',
		position: 'bottom-right',
	})
	clearTimeout(timer)
}

// 发送消息
const webSocketSend = (data) => {
	let code = ws?.readyState
	switch (code) {
		case 1:
			sendSock(data)
			break;
		case 2:
			ElNotification({
				title: 'WebSocket',
				message: 'WebSocket连接正在关闭中,请重新连接后再发送消息',
				type: 'warning',
				position: 'bottom-right',
			})
			break;
		default:
			ElNotification({
				title: 'WebSocket',
				message: '请先建立WebSocket连接',
				type: 'error',
				position: 'bottom-right',
			})
			break;
	}
}
function sendSock(data) {
	ws.send(JSON.stringify(data))
	ElNotification({
		title: 'WebSocket',
		message: '消息发送成功',
		type: 'success',
		position: 'bottom-right',
	})
}

// 关闭连接
const closeWebSocket = () => {
	if (isConnection()) ws.close()
}
// 是否已连接
function isConnection() {
	return ws?.readyState === 1
}

// 自定义事件
function receive(data) {
	let event = new CustomEvent('receive', { detail: data })
	window.dispatchEvent(event)
}
function connectStatus(status) {
	let event = new CustomEvent('connectStatus', { detail: status })
	window.dispatchEvent(event)
}

export default {
	connectWebsocket,
	closeWebSocket,
	webSocketSend,
	isConnection
}